package runningQueen.se_bigwork;

import java.io.File;
import java.io.IOException;

import javax.sound.sampled.AudioFormat;
import javax.sound.sampled.AudioInputStream;
import javax.sound.sampled.AudioSystem;
import javax.sound.sampled.DataLine;
import javax.sound.sampled.FloatControl;
import javax.sound.sampled.SourceDataLine;

/**
 * 播放SE【网上找的代码233
 * @author Administrator
 */
public class SEPlayer implements Runnable, IMusicPlayer {

	String fileurl = null;
	static FloatControl fc = null;
	AudioInputStream ais = null;
	SourceDataLine sdl = null;
	AudioFormat aif = null;
	DataLine.Info info = null;
	static double volume = 2.0;

	/**
	 * SE初始化
	 * @param path
	 */
	public SEPlayer(String path) {
		fileurl = path;
		try {
			// 由于初始化数据是在使用时才加载，而且音效不像BGM一开始就播放
			// 所以在调音效的时候会有报空指针
			// 所以需要先初始化载入信息
			init();
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	/**
	 * 设置声音的大小
	 * 
	 * @param newVolume
	 * <br />
	 *                如果直接输入电压值, 范围为0.0 ~ 2.0<br />
	 *                如果输入为百分比, 范围为0.0 ~ 100.0<br />
	 * @param isPercent
	 * <br />
	 *                如果输入为百分比, 则此处为true
	 */
	public static void setVolume(Double newVolume, boolean isPercent) {
		if (isPercent) {
			volume = newVolume / 50.0;
		}
		// 分贝的计算公式 dB = 20lg(E/Er) E-实际测量电压值，Er-参考电压值
		// 所输入的newVolume如果表示电压值则为E/Er
		float dB = (float) (Math.log(volume == 0.0 ? 0.0001 : volume)
				/ Math.log(10.0) * 20.0);
		fc.setValue(dB);
	}

	/**
	 * 获取声音的大小
	 * @return 当前声音的百分比
	 */
	public static int getValue() {
		return (int) volume * 50;
	}

	@Override
	public void play() throws IOException {
		// 我感觉这其实是用空间换效率的方法
		int nByte = 0;
		final int SIZE = 1024 * 64;
		byte[] buffer = new byte[SIZE];
		while (nByte != -1) {
			sdl.write(buffer, 0, nByte);
			nByte = ais.read(buffer, 0, SIZE);
		}
		sdl.stop();
	}

	@Override
	public void run() {
		try {
			init();
			play();
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	@Override
	public void init() throws Exception {
		ais = AudioSystem.getAudioInputStream(new File(fileurl));
		aif = ais.getFormat();
		// mp3转码
		if (fileurl.endsWith(".mp3") & aif.getEncoding() != AudioFormat.Encoding.PCM_SIGNED) {
			aif = new AudioFormat(
					AudioFormat.Encoding.PCM_SIGNED,
					aif.getSampleRate(),
					16, aif.getChannels(),
					aif.getChannels() * 2,
					aif.getSampleRate(),
					false);
			ais = AudioSystem.getAudioInputStream(aif,ais);
		}
		info = new DataLine.Info(
				SourceDataLine.class, aif);
		sdl = (SourceDataLine) AudioSystem.getLine(info);
		sdl.open(aif);
		sdl.start();
		fc = (FloatControl) sdl
				.getControl(FloatControl.Type.MASTER_GAIN);
		setVolume(volume, false);
	}
	
}
